/**
 * @addtogroup ffc_stream
 * ffc_stream
 * @{
 */
/**
 * @file         ffc_stream.h
 * @brief        流基础类
 * @note    
 * @author       尤胜坤[Akee](ysk@hopechart.com)
 * @date         2019-9-21
 * @version      1.0
 *
 * @par          修改日志
 * <table>
 * <tr><th>Date        <th>Version               <th>Author          <th>Description
 * <tr><td>2019-9-21   <td>1.0                   <td>Akee            <td>创建初始版本
 * @copyright    杭州鸿泉物联网技术股份有限公司
 */
#ifndef _MFC_STREAM_H_
#define _MFC_STREAM_H_

#include "ofc_object.h"
#include "ofc_types.h"
#ifdef __cplusplus
extern "C" {
#endif
/**
 * Seek模式
 */
enum TFfSeekOriginEnumTag
{
    kFfSeekOriginFromBegin    = 0,    ///< 从文件头开始向后移动
    kFfSeekOriginFromCurrent  = 1,    ///< 从文件的当前位置向后移动
    kFfSeekOriginFromEnd      = 2,    ///< 从文件的末尾开始向前移动
};
typedef enum TFfSeekOriginEnumTag TFfSeekOriginEnum;

/**
 * 流的通知事件
 * @param sender: 发起者
 * @param buffer: 缓冲地址
 * @param count: 大小
 * @return 实际的结果大小
 */
typedef Int32 (*TFfStreamNotifyEvent)(void *sender, void *buffer, Int32 count);

/**
 * 流的移动事件
 * @param sender: 发起者
 * @param offset: 偏移位置
 * @param origin: 偏移方式
 * @return 实际的位置
 */
typedef Int32 (*TFfStreamSeekEvent)(void *sender, Int32 offset, TFfSeekOriginEnum origin);

/**
 * 流的设置大小事件
 * @param sender: 发起者
 * @param new_size: 设置的新大小
 * @return True: 成功; False: 失败
 */
typedef Bool (*TFfStreamSetSizeEvent)(void *sender, Int32 new_size);



typedef struct TFfStreamTag TFfStream;
struct TFfStreamTag 
{
    TOfObject parent_;                ///< 父亲对象

PROTECTED
    TOfVirtualMethod Destroy_;        ///< 析构方法
    TFfStreamNotifyEvent OnRead;      ///< 读事件
    TFfStreamNotifyEvent OnWrite;     ///< 写事件
    TFfStreamSeekEvent  OnSeek;       ///< 移动事件
    TFfStreamSetSizeEvent OnSetSize;  ///< 设置大小事件
PRIVATE
};

/**
 * 构造函数
 * @param self: 对象指针
 * @return 
 */
void TFfStreamCreate(TFfStream *self);

/**
 * 从流的当前位置读取count字节到buffer
 * @param self: 对象指针
 * @param buffer: 存放数据的缓冲区
 * @param count: 读取的字节数
 * @return 返回实际读取到的字节数
 */
Int32 TFfStreamRead(TFfStream *self, void *buffer, Int32 count);

/**
 * 把buffer中的count个字节写入流的当前位置
 * @param self: 对象指针
 * @param buffer: 要写入的数据的缓冲区
 * @param count: 写入的字节数
 * @return 返回实际写入的字节数
 */
Int32 TFfStreamWrite(TFfStream *self, const void *buffer, Int32 count);

/**
 * 移动流的读取/写入点的位置
 * @param self: 对象指针
 * @param offset: 移动的偏移量.
 * @param origin: 移动的起点设置.
 *  kFfSeekOriginFromBegin: 从流的起点开始.即移动到流的offset位置
 *  kFfSeekOriginFromCurrent: 从当前的读取点开始.即移动到流的当前位置+offset的位置
 *  kFfSeekOriginFromEnd: 从流的末尾向前offset的位置.即移动到Stream.Size()-offset的位置
 * @return 返回移动后的位置
 */
Int32 TFfStreamSeek(TFfStream *self, Int32 offset, TFfSeekOriginEnum origin);

/**
 * 从流的当前位置读取count字节到buffer
 * @param self: 对象指针
 * @param buffer: 存放数据的缓冲区
 * @param count: 读取的字节数
 * @return 读取到的字节数为count,返回True,否则返回False
 */
Bool TFfStreamReadBuffer(TFfStream *self, void *buffer, Int32 count);

/**
 * 把buffer中的count个字节写入流的当前位置
 * @param self: 对象指针
 * @param buffer: 要写入的数据的缓冲区
 * @param count: 写入的字节数
 * @return 实际写入的字节数=count返回True,否则返回False
 */
Bool TFfStreamWriteBuffer(TFfStream *self, const void *buffer, Int32 count);

/**
 * 从source流的当前位置复制count个字节到本实例的当前位置
 * @param self: 对象指针
 * @param source: 源流
 * @param count: 复制的字节数
 * @return 返回实际复制的字节数
 */
Int32 TFfStreamCopyFrom(TFfStream *self, TFfStream *source, Int32 count);

/**
 * 返回流的当前读写位置
 * @param self: 对象指针
 * @return 位置
 */
Int32 TFfStreamPosition(TFfStream *self);

/**
 * 设置流的当前读写位置
 * @param self: 对象指针
 * @param pos: 从流的起点开始的位置
 * @return 实际设置的位置，从kFfSeekOriginFromBegin开始
 */
Int32 TFfStreamSetPosition(TFfStream *self, Int32 pos);

/**
 * 返回流的总大小; 注: 有些流是没有大小的,比如串口流
 * @param self: 对象指针
 * @return 大小
 */
Int32 TFfStreamSize(TFfStream *self);

/**
 * 设置流的大小; 注: 有些流是不能设置大小的,比如串口流
 * @param self: 对象指针
 * @param new_size: 新的大小
 * @return 实际设置的大小
 */
Bool TFfStreamSetSize(TFfStream *self, Int32 new_size);

#ifdef __cplusplus
}
#endif
#endif

/**
 * @} 
 */
